package cn.bonoon.services.plugins;

import java.text.SimpleDateFormat;
import java.util.ArrayList;
import java.util.Calendar;
import java.util.Date;
import java.util.HashMap;
import java.util.List;
import java.util.Map;

import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;

import cn.bonoon.core.plugins.VacationService;
import cn.bonoon.entities.plugins.VacationEntity;
import cn.bonoon.kernel.support.services.AbstractService;
import cn.bonoon.util.VacationInfo;

@Service
@Transactional(readOnly = true)
public class VacationServiceImpl extends AbstractService<VacationEntity> implements VacationService{

	@Override
	@Transactional(readOnly = true)
	public VacationInfo yearVacation(int year, long type, long user) {
		VacationEntity ve = get(year, type, user);
		if(null != ve) return new VacationInfo(ve);
		return null;
	}

	@Override
	public VacationEntity get(int year, long type, long user) {
		String ql = "from VacationEntity x where x.year=?1 and x.ownerId=?2 and x.ext=?3";
		return __first(domainClass, ql, year, user, type);
	}
	
	@Override
	public Date getAfter(Date date, int workDays, long ownerId) {
		Calendar cal = Calendar.getInstance();
		cal.setTime(date);
		int year = cal.get(Calendar.YEAR);
		int numberOfDay = 0;
		Map<String, String> holyDays = getMap(year, year+1,ownerId);
		while (numberOfDay < workDays) {
			cal.add(Calendar.DATE, 1);
			String key = sdf.format(cal.getTime());
			if (!holyDays.containsKey(key))// 如果碰到假日，顺延
				numberOfDay++;
		}
		//cal.setTime(date);
		//cal.add(Calendar.DATE, numberOfDay);
		return cal.getTime();
	}

	private Map<String, String> getMap(int fromYear, int toYear, long ownerId) {
		if (fromYear > toYear) {
			int temp = toYear;
			toYear = fromYear;
			fromYear = temp;
		}

		Map<String, String> map = new HashMap<String, String>();
		for (int year = fromYear; year <= toYear; year++) {
			String ql = "from VacationEntity x where x.year=?1 and x.ownerId=?2 and x.ext=?3";
			VacationEntity v = this.__first(VacationEntity.class,ql, year, ownerId, 1L);
			if(v == null){
				continue;
			}
			getHolyDays(year, 1, v.getJan(), map);
			getHolyDays(year, 2, v.getFeb(), map);
			getHolyDays(year, 3, v.getMar(), map);
			getHolyDays(year, 4, v.getApr(), map);
			getHolyDays(year, 5, v.getMay(), map);
			getHolyDays(year, 6, v.getJun(), map);
			getHolyDays(year, 7, v.getJul(), map);
			getHolyDays(year, 8, v.getAug(), map);
			getHolyDays(year, 9, v.getSep(), map);
			getHolyDays(year, 10, v.getOct(), map);
			getHolyDays(year, 11, v.getNov(), map);
			getHolyDays(year, 12, v.getDec(), map);
		}

		return map;
	}

	private void getHolyDays(int year, int month, String dayStr,
			Map<String, String> map) {
		List<Date> r = new ArrayList<Date>();
		String[] days = dayStr.split(",");
		Calendar cal = Calendar.getInstance();
		for (String d : days) {
			cal.set(year,month-1,Integer.parseInt(d));			
			map.put(sdf.format(cal.getTime()),"");
		}
	}

	final SimpleDateFormat sdf = new SimpleDateFormat("yyyy年MM月dd日");
	@Override
	public Date getBefore(Date date, int workDays, long ownerId) {
		Calendar cal = Calendar.getInstance();
		cal.setTime(date);
		int year = cal.get(Calendar.YEAR);
		int numberOfDay = 0;
		Map<String, String> holyDays = getMap(year, year,ownerId);
		while (numberOfDay < workDays) {
			cal.add(Calendar.DATE, -1);
			String key = sdf.format(cal.getTime());
			if (!holyDays.containsKey(key))// 如果碰到假日，顺延
				numberOfDay++;
		}		

		return cal.getTime();
	}

}
